package vip.xiaonuo.modular.attendancerecord.service;

import lombok.extern.slf4j.Slf4j;
import org.jetbrains.annotations.NotNull;
import org.springframework.stereotype.Service;
import vip.xiaonuo.core.exception.ServiceException;
import vip.xiaonuo.core.util.DateUtils;
import vip.xiaonuo.facedoor.modular.memberuser.entity.MemberUser;
import vip.xiaonuo.modular.attendancedayset.entity.AttendanceDaySet;
import vip.xiaonuo.modular.attendancedayset.param.AttendanceDaySetParam;
import vip.xiaonuo.modular.attendancegroup.entity.AttendanceGroup;
import vip.xiaonuo.modular.attendancerecord.entity.AttendanceRecord;
import vip.xiaonuo.modular.attendanceshift.entity.AttendanceShift;

import java.util.ArrayList;
import java.util.Calendar;
import java.util.Date;
import java.util.List;

@Service
@Slf4j
public class AttendancePlanService_OneDay extends AttendancePlanBaseService{



    public void createPlan(AttendanceGroup group){
        super.check(group);
        // 获取人员
        List<MemberUser> users = super.getMemberUsers(group.getOrgIds());
        if(users == null || users.size() == 0){
            throw new ServiceException(500,"用户组下没有用户！");
        }
        log.info("考勤组：{} 参与考勤人数：{}" ,group.getGroupName() , users.size() );
        // 获取班次
        List<AttendanceShift> shifts = super.getAttendanceShifts(group.getAttendanceShiftIds());
        if(shifts == null || shifts.size() == 0){
            throw new ServiceException(500,"未定义班次！");
        }
        log.info("考勤组：{} 考勤班次数量：{}" ,group.getGroupName() , shifts.size() );
        Date date = this.getAttendanceDay(group);
        if(date==null){
            throw new ServiceException(500,"明天不是工作日");
        }
        log.info("考勤日期: {}" , DateUtils.formatDate(date));
        // 循环生成考勤计划
        List<AttendanceRecord> toSave = new ArrayList<>();

        this.doCreatePlan(toSave,date,group,users,shifts);
        log.info("待保存考勤计划: {}" , toSave.size());

        if( toSave.size() == 0){
            throw new ServiceException(500,"未保存任何数据！");
        }

        recordService.saveBatch(toSave);
        log.info("考勤计划生成成功");
    }

    private Date getAttendanceDay(@NotNull AttendanceGroup group) {
        int daySource = group.getWorkDaysSource();

        Calendar cal = Calendar.getInstance();
        cal.add(Calendar.DATE,1);
        Date nextDay = cal.getTime();

        if(daySource == 0 ){ // 法定(需要外网接口，暂不处理)
            return nextDayIsWorkDay(nextDay) ? nextDay : null;
        }else if(daySource == 1){ // 排除节假日
            return isNextDayNotInHolidays(nextDay) ? nextDay : null;
        }else if(daySource == 2){ // 仅自定义工作日
            return isNextDayInWorkDays(nextDay) ? nextDay : null;
        }else if(daySource == 3){ // 自定义排班
            return null;
        }
        return null;
    }




    /**
     * 排除节假日
     * @return
     */
    private boolean isNextDayNotInHolidays(Date nextDay) {
        AttendanceDaySetParam param = new AttendanceDaySetParam();
        param.setWorkdayOrHoliday(1);
        param.setMonth(sdf_ym.format(nextDay));
        List<AttendanceDaySet> daySets = daySetMapper.listMonth(param);

        return !isBetween(nextDay,daySets);
    }

    /**
     * 仅工作日
     * @return
     */
    private boolean isNextDayInWorkDays(Date nextDay) {
        AttendanceDaySetParam param = new AttendanceDaySetParam();
        param.setWorkdayOrHoliday(2);
        param.setMonth(sdf_ym.format(nextDay));
        List<AttendanceDaySet> daySets = daySetMapper.listMonth(param);

        return isBetween(nextDay,daySets);
    }



}
